import { Table, TableUrl } from '../types/interface';
import { reactive, computed, toRefs } from 'vue';
import { axios } from '@/uni_modules/dx-admin/api/index';
/**
 * @description table 页面操作方法封装
 * @param {Object} urls 表格数据 urls (必传)
 * @param {Object} funcName 云函数名称 funcName (必传)
 * @param {Boolean} isPagination 是否有分页(非必传，默认为true)
 * @param {String} order 排序字段
 * @param {String} sort 排序规则
 * @param {behaviorEvent} behaviorEvent 行为事件
 * */
export const useTable = (urls: TableUrl, funcName: string, isPagination: boolean, order: string, sort: string, behaviorEvent?: any) => {
	const state = reactive<Table.TableStateProps>({
		// 表格数据
		tableData: [],
		// 分页数据
		pagination: {
			// 当前页数
			page: 1,
			// 每页显示条数
			size: 10,
			// 总条数
			total: 0,
		},
		// 初始化默认的查询参数
		searchInitParam: {},
		// 总参数(包含分页和查询参数)
		totalParam: {},
		// tabs 参数
		tabsParam: {},
		// 是否加载中
		isLoading: false,
	});

	/**
	 * @description 分页查询参数(只包括分页和表格字段排序,其他排序方式可自行配置)
	 * */
	const pageParam = computed({
		get: () => {
			return {
				page: state.pagination.page,
				size: state.pagination.size,
			};
		},
		set: (newVal: any) => {
			console.log('我是分页更新之后的值', newVal);
		},
	});

	/**
	 * @description 获取表格数据
	 * @return void
	 * */
	const getTableList = () => {
		state.isLoading = true;
		return new Promise(async (resolve, reject) => {
			try {
				// 先把初始化参数和分页参数放到总参数里面
				Object.assign(state.totalParam, isPagination ? pageParam.value : {});
				let params = state.totalParam;
				// 处理排序
				params.order = order || '_id';
				params.sort = sort || 'desc';
				if (typeof behaviorEvent?.onBeforeIndex === 'function') {
					let resParam = behaviorEvent.onBeforeIndex(params);
					if (resParam === false) return;
					// 处理后的查询参数
					if (!!resParam) params = resParam;
				}
				// 去请求
				const { data, code, message } = await axios.send(urls.index, funcName, params);
				if (code === 1000) {
					let list = data.list === void 0 ? data : data.list;
					if (typeof behaviorEvent?.onAfterIndex === 'function') {
						let resList = behaviorEvent.onAfterIndex(list);
						if (resList === false) return;
						//处理之后的数据
						if (!!resList) list = resList;
					}
					state.tableData = list;
					state.pagination.total = data.total || 0;
				} else {
					ElMessage.error(message);
				}
				state.isLoading = false;
				resolve(true);
			} catch (error) {
				console.error(error);
				state.isLoading = false;
				reject(error);
			}
		});
	};

	/**
	 * @description 更新查询参数
	 * @return void
	 * */
	const updatedTotalParam = (searchParam?: any) => {
		state.totalParam = {};
		// 处理查询参数，可以给查询参数加自定义前缀操作
		let nowSearchParam: { [key: string]: any } = {};
		// 防止手动清空输入框携带参数（这里可以自定义查询参数前缀）
		if (searchParam && typeof searchParam === 'object') {
			for (let key in searchParam) {
				let value = searchParam[key];
				if (value || value === false || value === 0) {
					nowSearchParam[key] = searchParam[key];
				}
			}
		}
		Object.assign(state.totalParam, state.tabsParam, nowSearchParam, isPagination ? pageParam.value : {});
	};

	/**
	 * @description 表格数据查询
	 * @return void
	 * */
	const search = (param: any) => {
		state.pagination.page = 1;
		updatedTotalParam(param);
		getTableList();
	};

	/**
	 * @description 表格数据重置
	 * @return void
	 * */
	const reset = () => {
		state.pagination.page = 1;
		let searchParam: any = {};
		// 重置搜索表单的时，如果有默认搜索参数，则重置默认的搜索参数
		for (let [key, value] of Object.entries(state.searchInitParam)) {
			searchParam[key] = value;
		}
		updatedTotalParam(searchParam);
		getTableList();
	};

	/**
	 * @description 每页条数改变
	 * @param {Number} val 当前条数
	 * @return void
	 * */
	const handleSizeChange = (val: number) => {
		state.pagination.page = 1;
		state.pagination.size = val;
		getTableList();
	};

	/**
	 * @description 当前页改变
	 * @param {Number} val 当前页
	 * @return void
	 * */
	const handleCurrentChange = (val: number) => {
		state.pagination.page = val;
		getTableList();
	};

	/**
	 * 删除
	 * @param ids
	 * @returns
	 */
	const deleteTableRows = (ids: any) => {
		return new Promise(async (resolve, reject) => {
			try {
				if (typeof behaviorEvent?.onBeforeDelete === 'function') {
					let resParam = behaviorEvent.onBeforeDelete(ids);
					if (resParam === false) return;
					// 处理后的查询参数
					if (!!resParam) ids = resParam;
				}
				// 去请求
				const { code, message } = await axios.send(urls.del, funcName, { ids });
				if (code === 1000) {
					if (typeof behaviorEvent?.onAfterDelete === 'function') {
						let res = behaviorEvent.onAfterDelete();
						if (res === false) return;
					}
					getTableList();
				} else {
					ElMessage.error(message);
				}
				resolve(true);
			} catch (error) {
				console.error(error);
				reject(error);
			}
		});
	};

	/**
	 *  批量更新
	 * @param row
	 * @param field
	 * @returns
	 */
	const multiTableRows = (row: any, field: string) => {
		return function (): Promise<boolean> {
			row.switchLoading = {
				[field]: true,
			};
			return new Promise(async (resolve) => {
				try {
					// 去请求
					const { code, message } = await axios.send(urls.multi, funcName, { id: row._id, field, value: !row[field] });
					row.switchLoading[field] = false;
					if (code === 1000) {
						resolve(true);
					} else {
						ElMessage.error(message);
						resolve(false);
					}
				} catch (error: any) {
					ElMessage.error(error.message);
					row.switchLoading[field] = false;
					resolve(false);
				}
			});
		};
	};

	return {
		...toRefs(state),
		getTableList,
		deleteTableRows,
		search,
		reset,
		handleSizeChange,
		handleCurrentChange,
		multiTableRows,
	};
};
